<?php

class WSB_Model2
{

    /**
     * @var array
     */
    protected $_data = array();

    /**
     * @var WSB_DbMapper
     */
    protected $_mapper;

    
    /**
     * Constructor
     *
     * @param array|object $data
     * @param boolean $useSetters
     */
    public function __construct($data=null, $useSetters=false)
    {
        if(!is_null($data)) {
            $this->populate($data, $useSetters);
        }
        $this->init();
    }

    /**
     * Initialize object
     *
     * Called from {@link __construct()} as final step of object instantiation.
     *
     * @return void
     */
    public function init()
    {
    }

    /**
     * @param array|object $data
     * @param boolean $useSetters
     */
    public function populate($data, $useSetters=false)
    {
        if(is_object($data)) {
            $data = (array)$data;
        }
        if(!is_array($data)) {
            $exception = sprintf('Initial data in "%s"::populate() must be an array or object', get_class($this));
            throw new Exception($exception);
        }
        if(!$useSetters) {
            $this->_data = array_merge($this->_data, $data);
        } else {
            foreach($data AS $key=>$value) {
                $this->__set($key, $value);
            }
        }
    }

    /**
     * @param WSB_DbMapper $mapper
     */
    public function setMapper(WSB_DbMapper $mapper)
    {
        $this->_mapper = $mapper;
    }

    /**
     * @return WSB_DbMapper
     */
    public function getMapper()
    {
        return $this->_mapper;
    }

    /**
     * @param string $name
     * @param mixed $value
     */
    protected function __set($name, $value)
    {
        if(substr($name, 0, 1) == '_') {
            $exception = sprintf('Invalid property "%s" in class "%s"', $name, get_class($this));
            throw new Exception($exception);
        }
        $method = 'set' . $name;
        if (method_exists($this, $method)) {
            $this->$method($value);
        } else {
            $this->_data[$name] = $value;
        }
    }

    /**
     * @param string $name
     * @return mixed
     */
    protected function __get($name)
    {
        if(substr($name, 0, 1) == '_') {
            $exception = sprintf('Invalid property "%s" in class "%s"', $name, get_class($this));
            throw new Exception($exception);
        }
        $method = 'get' . $name;
        if (method_exists($this, $method)) {
            return $this->$method();
        } else {
            if(!array_key_exists($name, $this->_data)) {
                $message = sprintf('Property "%s" does not exist in class "%s"', $name, get_class($this));
                trigger_error($message, E_USER_NOTICE);
                return null;
            }
            return $this->_data[$name];
        }
    }

    /**
     * @param string $name
     * @return boolean
     */
    protected function __isset($name)
    {
        return isset($this->_data[$name]);
    }

    /**
     * @param string $name
     */
    protected function __unset($name)
    {
        unset($this->_data[$name]);
    }

    /**
     * @param boolean $useGetters
     * @return array
     */
    public function toArray($useGetters=false)
    {
        if(!$useGetters) {
            return $this->_data;
        } else {
            $data = array();
            foreach($this->_data AS $key=>$value) {
                $data[$key] = $this->__get($key);
            }
            return $data;
        }
    }

    /**
     * @param boolean $useGetters
     * @return string
     */
    public function toJson($useGetters=false)
    {
        $data = $this->toArray($useGetters);
        return json_encode($data);
    }

    /**
     * @param boolean $useGetters
     * @return string
     */
    public function toXml($useGetters=false)
    {
    }

    /**
     * Get the form editor for this table row, overwritten with config settings if INI-file exists.
     *
     * @return WSB_Form
     */
    public function getForm()
    {
        $form = new Zend_Form();
        $form->addElementPrefixPath('WSB_Filter', 'WSB/Filter', 'filter');
        $form->addElementPrefixPath('WSB_Validator', 'WSB/Validator', 'validate');
		$form->addPrefixPath('WSB_Form_Element', 'WSB/Form/Element', 'element');

        $form->removeDecorator('HtmlTag');
        //$form->addDecorator(array('FooBar' => 'HtmlTag'), array('tag' => 'div'));

        $config = new Zend_Config(array(
            'method' => 'post',
            'action' => $_SERVER['REQUEST_URI']
        ));
        $form->setConfig($config);

        $formKey = get_class($this);
        
        if(isset($GLOBALS['WSB']['forms'][$formKey]['elements'])) {
            $elements = $GLOBALS['WSB']['forms'][$formKey]['elements'];
            $buttons = array(
                '_save' => array(
                    'type' => 'submit',
                    'options' => array(
                        'label' => 'Submit'
                    )
                ),
                '_saveAndClose' => array(
                    'type' => 'submit',
                    'options' => array(
                        'label' => 'Submit/Close document'
                    )
                ),
                '_cancel' => array(
                    'type' => 'submit',
                    'options' => array(
                        'label' => 'Cancel'
                    )
                )
            );
            $form->addElements($elements);
            $form->addElements($buttons);
        }

        if(isset($GLOBALS['WSB']['forms'][$formKey]['displayGroups'])) {
            $displayGroups = $GLOBALS['WSB']['forms'][$formKey]['displayGroups'];
            $form->addDisplayGroups($displayGroups);
        }

        $form->addDisplayGroups(array('buttons' => array('_save', '_saveAndClose', '_cancel')));
        $displayGroup = $form->getDisplayGroup('buttons');
        $displayGroup->addAttribs(array('class' => 'fieldset-buttons'));

        foreach($form->getDisplayGroups() AS $dg) {
            $dg->removeDecorator('DtDdWrapper');
        }
        $this->optimizeForm($form);

        return $form;
    }

    public function optimizeForm($form)
    {
        $hiddens = array();
        $elements = $form->getElements();
        
        // Setze Default CSS-Klasse
        foreach($elements AS $element) {
            if($element instanceof Zend_Form_Element) {
                $label = $element->getDecorator('label');
                if($label instanceof Zend_Form_Decorator_Label) {
                    $label->setRequiredSuffix('*');
                }

                $class = '';
                switch($element->getType()) {
                    case 'Zend_Form_Element_Text':
                        $class = 'form-default-element-text';
                    break;
                    case 'Zend_Form_Element_Textarea':
                        $class = 'form-default-element-textarea';
                    break;
                    case 'Zend_Form_Element_Password':
                        $class = 'form-default-element-password';
                    break;
                    case 'Zend_Form_Element_Checkbox':
                        $class = 'form-default-element-checkbox';
                    break;
                    case 'WSB_Form_Element_RTE':
                        $class = 'form-default-element-rte';
                    break;
                    case 'Zend_Form_Element_Select':
                        $class = 'form-default-element-select';
                    break;
                    case 'WSB_Form_Element_SelectCsvAdvImages':
                        $class = 'form-default-element-select';
                    break;
                }
                $element->setAttrib('class', $class);
            }
        }

        foreach($form->getDisplayGroups() AS $dg) {
            foreach($dg->getElements() AS $el) {
                if($el instanceof Zend_Form_Element_Hidden) {
                    $dg->removeElement($el->getName());
                    $hiddens[] = $el->getName();
                    $el->setDecorators(array('ViewHelper'));
                }
            }
        }

        $form->addDisplayGroup($hiddens, 'hiddenfields');
        $displayGroup = $form->getDisplayGroup('hiddenfields');
        $displayGroup->removeDecorator('DtDdWrapper');
        $displayGroup->removeDecorator('Fieldset');
        $displayGroup->removeDecorator('HtmlTag');
        //$displayGroup->removeDecorator('FormElements');
    }

	/**
	 * @todo: Hier sind dringend Anpassungen notwendig!
	 * @param string $key
	 * @return string
	 */
	public function translate($key)
	{
		static $translate = null;
		if(empty($translate)) {
			$translate = Zend_Registry::get('Zend_Translate');
			$segments = explode('_', get_class($this));
            out($this);
			if(count($segments) > 0) {
				$locale = Zend_Registry::get('Zend_Locale');
				// Neue Version
				$translation = sprintf('%s%s/i18n/tables/%s.%s.csv',
					WSB_MODULES_PATH,
					strtolower($segments[0]), // Modulname
					$this->getName(),
					$locale
				);
				if(is_file($translation)) {
					$translate->addTranslation($translation, $locale);
				}
				// Übergangs-Version
				$translation = sprintf('%s%s/models/table.%s.csv', WSB_XTENSION_PATH, strtolower($segments[0]), $locale);
				if(is_file($translation)) {
					$translate->addTranslation($translation, $locale);
				}
				// Alte Version
				$segments[count($segments)-1] = 'table.'.$locale.'.csv';
				$translation = WSB_PATH . implode('/', $segments);
				if(is_file($translation)) {
					$translate->addTranslation($translation, $locale);
				}
			}
		}
		return $translate->_($key);
	}
    
}
